#include <my_header.h>
#include "InternetOperator.h"
#include "Analysis.h"
#include "Stack.h"
#include "Usr.h"
#include "putsDispose.h"
#include "getsDispose.h"
#include "pwdDispose.h"
#include "lsDispose.h"
#include "cdDispose.h"
#include "mkdirDispose.h"
#include "rmdirDispose.h"
#include "rmfileDispose.h"





int main()
{
    char * ip = "192.168.220.128";
    char * port = "8888";
    int sockfd = socket(AF_INET,SOCK_STREAM,0);
    struct sockaddr_in addr;
    addr.sin_family = AF_INET;
    addr.sin_port = htons(atoi(port));
    addr.sin_addr.s_addr = inet_addr(ip);
    connect(sockfd,(struct sockaddr *)&addr,sizeof(addr));

    int epollfd = epoll_create(1);
    epollAdd(epollfd,sockfd);
    struct epoll_event ready_set[5];

    Stack * s = (Stack *)calloc(1,sizeof(Stack));   //路径栈
    stackInit(s);
    char * bottom = (char *)calloc(2,sizeof(char));
    bottom[0] = '/';     
    push(s,bottom);

    char buf[4096] = {0};

    int flag = 0;      //标记客户端或服务端主动退出

    epollAdd(epollfd,STDIN_FILENO);
    /////////////////////////////////////////////////////////////////////////////////
    Usr usr;
    bzero(&usr,sizeof(usr));
    while(1){
        printf("注册y,登录n\n");
        char c;
        scanf("%c",&c);
        send(sockfd,&c,1,0);
        if(c == 'y'){//进入注册语句
            while(1){
                printf("已进入注册！\n");
                printf("请输入用户名！\n");
                scanf("%s",usr.usrname);
                printf("请输入密码！\n");
                scanf("%s",usr.password);
                // 清空输入缓冲区
                int ch;
                while ((ch = getchar()) != '\n');
                int length = sizeof(usr); 
                send(sockfd,&length,sizeof(int),0);
                send(sockfd,&usr,length,0);
                char signal = '\0';
                while(1){//等待服务器发送注册成功信号
                    int readynum = epoll_wait(epollfd,ready_set,5,-1);
                    for(int i = 0; i < readynum ; ++i){
                        if(ready_set->data.fd == sockfd){
                            recv(sockfd,&signal,1,0);
                            printf("signal = %c\n",signal);
                            if(signal == 'y'){
                                printf("注册成功!\n");
                            }
                            else{
                                printf("注册失败！\n");
                            }
                            break;
                        }
                    }
                    break;
                }
                break;
            }
        }
        else if(c == 'n'){//进入登录语句
            while(1){
                printf("已进login！\n");
                printf("请输入用户名！\n");
                scanf("%s",usr.usrname);
                printf("请输入密码！\n");
                scanf("%s",usr.password);
                int length = sizeof(usr);
                send(sockfd,&length,sizeof(int),0);
                send(sockfd,&usr,length,0);
                char signal2 = '\0';
                while(1){//等待服务器发送登录成功信号
                    int readynum = epoll_wait(epollfd,ready_set,5,-1);
                    for(int i = 0; i < readynum ; ++i){
                        if(ready_set->data.fd == sockfd){
                            recv(sockfd,&signal2,1,0);
                            printf("signal2 = %c\n",signal2);
                            if(signal2 == 'y'){
                                printf("登录成功!\n");
                            }
                            else{
                                printf("登录失败！\n");
                            }
                            break;
                        }
                    }
                    break;
                }            
                if(signal2 == 'y'){
                    break;//登录成功跳出登录语句
                }
                else{
                    continue;//登录失败继续循环
                }
            }
        }
        else{
            printf("非法字符，请重新输入\n");
            // 清空输入缓冲区
            int ch;
            while ((ch = getchar()) != '\n');
            continue;
        }
        if(c == 'y'){
            continue;
        }
        break;
    }

    //////////////////////////////////////////////////////////////////////////////////
    while(1){
        char s_curpath[256] = {0};      
        if(s->size == 1){      
            s_curpath[0] = '/';
        }else{
            for(int i = 1 ; i < s->size ;++i){
                char xiegang[] = "/";
                char ass_p[64] = {0};
                memcpy(ass_p,s->str[i],strlen(s->str[i]));
                strcat(s_curpath,xiegang);
                strcat(s_curpath,ass_p);
            }
        }
        s_curpath[strlen(s_curpath)] = '$';
        printf("%s",s_curpath);
        fflush(stdout);
        int epoll_ret = epoll_wait(epollfd,ready_set,5,-1);     
        for(int i = 0 ; i < epoll_ret ; ++i){
            if(ready_set[i].data.fd == STDIN_FILENO){
                bzero(buf,sizeof(buf));
                int rret = read(STDIN_FILENO,buf,sizeof(buf));
                if(buf[0] == '\n'){
                    break;
                }
                if(rret == 0){
                    flag = 1;   
                    break;
                }
                int pose_ret;
                char * p ;
                char * cpath;
                char * spath;
                switch (analysis(buf,sockfd)) {   // 不同命令返回值不同，根据返回值判断时候向后台传参
                case 0:
                    pose_ret = cdDispose(buf,sockfd,s);  //一、更新并检查路径对不对。（防止越界）二、向后台发送路径看有没有 三、更新路径栈
                    /* printf("cd返回值%d\n",pose_ret); */
                    break;
                case 1:
                    lsDispose(sockfd,s_curpath);
                    break;
                case 2:
                    pwdDispose(s);
                    break;
                case 3:
                    p = checkPath(buf,s,0);
                    if(p == NULL){
                        break;
                    }
                    mkdirDispose(p,sockfd,s_curpath);
                    break;
                case 4:
                    p = checkPath(buf,s,0);
                    if(p==NULL){
                        break;
                    }
                    rmdirDispose(p,sockfd);
                    break;
                case 5:
                    p = checkPath(buf,s,0);
                    if(p == NULL){
                        break;
                    }
                    rmfileDispose(p,sockfd);
                    break;
                case 6:
                    strtok(buf," ");
                    cpath = strtok(NULL," ");
                    spath = strtok(NULL," ");
                    if(spath != NULL){
                        p = checkPath(spath,s,1);
                    }else{
                        char ass_p[] = "./";
                        p = checkPath(ass_p,s,1);
                        if( p == NULL ){
                            break;
                        }
                    }
                    printf("p:%s\n",p);
                    pose_ret = putsDispose(sockfd,cpath,p);    // 输入信息、套接字、服务器当前工作目录
                    printf("puts返回值%d\n",pose_ret);
                    break;
                case 7:
                    strtok(buf," ");
                    spath = strtok(NULL," ");
                    cpath = strtok(NULL," ");
                    if(spath != NULL){
                        p = checkPath(spath,s,1);
                    }else{
                        char ass_p[] = "./";
                        p = checkPath(ass_p,s,1);
                        if( p == NULL ){
                            break;
                        }
                    }
                    printf("p:%s\n",p);
                    pose_ret = getsDispose(sockfd,p,cpath);    
                    printf("gets返回值%d\n",pose_ret);
                    break;
                default:
                    printf("未知命令\n");
                    break;
                }
            }else if(ready_set[i].data.fd == sockfd){
                bzero(buf,sizeof(buf));
                int rret = recv(sockfd,buf,sizeof(buf),MSG_WAITALL);
                if(rret == 0){
                    flag = 1;
                    break;
                }
            }
        }
        if(flag == 1){
            break;
        }
    }
    return 0;
}

